package com.techsoul.module.pms.service.impl;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.techsoul.common.core.exception.BusinessException;
import com.techsoul.common.core.exception.ParamException;
import com.techsoul.common.core.pojo.vo.UserVo;
import com.techsoul.common.core.util.ServletUtils;
import com.techsoul.common.core.util.bean.BeanUtils;
import com.techsoul.common.core.util.collection.ListUtils;
import com.techsoul.common.core.util.id.IdWorker;
import com.techsoul.common.core.util.lang.NumberUtils;
import com.techsoul.common.security.service.TokenService;
import com.techsoul.module.basic.mapper.HrEmployeeManageMapper;
import com.techsoul.module.basic.pojo.entity.HrEmployeeManage;
import com.techsoul.module.basic.pojo.vo.HrEmployeeManageVo;
import com.techsoul.module.basic.service.IHrEmployeeManageService;
import com.techsoul.module.goods.mapper.SkuMapper;
import com.techsoul.module.goods.mapper.SpuMapper;
import com.techsoul.module.goods.pojo.entity.Sku;
import com.techsoul.module.goods.pojo.entity.Spu;
import com.techsoul.module.goods.pojo.vo.SkuVo;
import com.techsoul.module.pms.enmus.WmsInStatusEnum;
import com.techsoul.module.pms.enmus.WmsOutStatusEnum;
import com.techsoul.module.pms.mapper.*;
import com.techsoul.module.pms.pojo.entity.*;
import com.techsoul.module.pms.pojo.param.*;
import com.techsoul.module.pms.pojo.vo.*;
import com.techsoul.module.pms.service.ITWmsReciptIntoLocPlanService;
import com.techsoul.module.pms.service.ITbWmsLocationService;
import com.techsoul.module.pms.service.ITbWmsMaterialDeliveryLineService;
import com.techsoul.module.pms.service.ITbWmsMaterialReceiptLineService;
import com.techsoul.module.system.enmus.UserType;
import com.techsoul.module.system.mapper.ConfigMapper;
import org.apache.poi.hpsf.Decimal;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;

/**
 * 上架计划 Service实现
 *
 * @author liuen
 * @date 2023-03-28
 */
@Service
@Transactional(readOnly = true)
public class TWmsReciptIntoLocPlanServiceImpl implements ITWmsReciptIntoLocPlanService {

    @Autowired
    private IdWorker idWorker;

    @Autowired
    private TWmsReciptIntoLocPlanMapper mapper;

    @Autowired
    private TbWmsMaterialReceiptLineMapper tbWmsMaterialReceiptLineMapper;
    @Autowired
    private IHrEmployeeManageService iHrEmployeeManageService;
    @Autowired
    private ITbWmsMaterialReceiptLineService iTbWmsMaterialReceiptLineService;
    @Autowired
    private ITbWmsMaterialDeliveryLineService iTbWmsMaterialDeliveryLineService;
    @Autowired
    private ITbWmsLocationService iTbWmsLocationService;
    @Autowired
    private TWhWarehouseCustomerMaterialMapper tWhWarehouseCustomerMaterialMapper;
    @Autowired
    private TbWmsLocationMapper tbWmsLocationMapper;
    @Autowired
    private HrEmployeeManageMapper hrEmployeeManageMapper;
    @Autowired
    private TbWmsMaterialDeliveryLineMapper tbWmsMaterialDeliveryLineMapper;
    @Autowired
    private TbWmsMaterialInLocationMapper tbWmsMaterialInLocationMapper;

    @Autowired
    private ConfigMapper configMapper;
    @Autowired
    private SkuMapper skuMapper;
    @Autowired
    private TokenService tokenService;

    /**
     * 新增
     * @param params
     * @return
     */
    @Transactional(readOnly = false)
    @Override
    public String insert(TWmsReciptIntoLocPlanSaveParam params) {
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        TWmsReciptIntoLocPlan entity = new TWmsReciptIntoLocPlan();
        BeanUtils.copyProperties(params, entity);
        entity.setId(idWorker.nextId() + "").preInsert(user.getId());
        this.mapper.insert(entity);
        return entity.getId();
    }
    @Transactional(readOnly = false)
    @Override
    public String putInLoc(String locationNo,String containerNo,String lotNo, String [] ids){
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        TbWmsLocation loc = this.tbWmsLocationMapper.findByLocationNo(locationNo);
        double currentLoad = loc.getCurrentLoad();
        double remainLoad = loc.getRemainLoad();
        List<String> lineids = new ArrayList<String>();
        double max = loc.getMaxLoad();
        for(int i=0; i <ids.length;i++){
            String putinLocId = (String)ids[i];
            TWmsReciptIntoLocPlan tWmsReciptIntoLocPlan = this.mapper.selectById(putinLocId);
            tWmsReciptIntoLocPlan.setStatus(WmsInStatusEnum.inposition.getValue());
            tWmsReciptIntoLocPlan.preUpdate(user.getId());
            this.mapper.updateById(tWmsReciptIntoLocPlan);

            TbWmsMaterialReceiptLine  tbWmsMaterialReceiptLine = this.tbWmsMaterialReceiptLineMapper.selectById(tWmsReciptIntoLocPlan.getReciptLineId());
            tbWmsMaterialReceiptLine.setStatus(WmsInStatusEnum.inposition.getValue());
            tbWmsMaterialReceiptLine.setStageNo(locationNo);
            tbWmsMaterialReceiptLine.preUpdate(user.getId());
            lineids.add(tbWmsMaterialReceiptLine.getId());
            this.tbWmsMaterialReceiptLineMapper.updateById(tbWmsMaterialReceiptLine);

            TbWmsMaterialInLocation tbWmsMaterialInLocation = new TbWmsMaterialInLocation();
            tbWmsMaterialInLocation.setLocationNo(locationNo);
            tbWmsMaterialInLocation.setArea(loc.getArea());
            tbWmsMaterialInLocation.setTier(loc.getTier());
            tbWmsMaterialInLocation.setSkuCode(tbWmsMaterialReceiptLine.getSkuCode());
            tbWmsMaterialInLocation.setBin(loc.getBin());
            tbWmsMaterialInLocation.setBay(loc.getBay());
            tbWmsMaterialInLocation.setLotNo(lotNo);
            tbWmsMaterialInLocation.setCellNo(containerNo);
            tbWmsMaterialInLocation.setCustomerId(tbWmsMaterialReceiptLine.getCustomerNo());
            tbWmsMaterialInLocation.setMaterialNo(tbWmsMaterialReceiptLine.getMaterialNo());
            tbWmsMaterialInLocation.setMaterialName(tWmsReciptIntoLocPlan.getMaterialName());
            tbWmsMaterialInLocation.setReceivedLineId(tbWmsMaterialReceiptLine.getId());
            tbWmsMaterialInLocation.setQuantity(tWmsReciptIntoLocPlan.getQty().doubleValue());
            double rate = NumberUtils.div(tWmsReciptIntoLocPlan.getQty().doubleValue(),tbWmsMaterialReceiptLine.getQuantity());
            if(tbWmsMaterialReceiptLine.getVolume()!=null){
                Double volume = NumberUtils.mul(tbWmsMaterialReceiptLine.getVolume(),rate);
                tbWmsMaterialInLocation.setVol(volume);
                currentLoad = NumberUtils.add(currentLoad,volume);
                remainLoad =NumberUtils.sub(max,currentLoad);
            }else{
                TWhWarehouseCustomerMaterial tWhWarehouseCustomerMaterialVo =
                        this.tWhWarehouseCustomerMaterialMapper.findBySkuCode(tbWmsMaterialReceiptLine.getSkuCode());
                Double volume = NumberUtils.mul(tWhWarehouseCustomerMaterialVo.getUnitVolume().doubleValue(),tbWmsMaterialReceiptLine.getQuantity());
                volume = NumberUtils.mul(volume,rate);
                tbWmsMaterialInLocation.setVol(volume);
                currentLoad = NumberUtils.add(currentLoad,volume);
                remainLoad =NumberUtils.sub(max,currentLoad);
            }
            if(tbWmsMaterialReceiptLine.getWeight()!=null){
                Double wt = NumberUtils.mul(tbWmsMaterialReceiptLine.getWeight(),rate);
                tbWmsMaterialInLocation.setWeight(wt);

            }

            tbWmsMaterialInLocation.setSiteCode(tbWmsMaterialReceiptLine.getSite());
            tbWmsMaterialInLocation.setStatus(WmsInStatusEnum.inposition.getValue());
            tbWmsMaterialInLocation.setId(idWorker.nextId() + "").preInsert(user.getId());
            this.tbWmsMaterialInLocationMapper.insert(tbWmsMaterialInLocation);


        }
        loc.setRemainLoad(remainLoad);
        loc.setCurrentLoad(currentLoad);
        loc.preUpdate(user.getId());
        this.tbWmsLocationMapper.updateById(loc);
        this.iTbWmsMaterialReceiptLineService.generateArForReceipt(lineids);
        return "success";
    }
    /**
     * 删除
     * @param id
     * @return
     */
    @Transactional(readOnly = false)
    @Override
    public Integer delete(String id) {
        return this.mapper.deleteById(id);
    }

    /**
     * 批量删除
     * @param idList
     */
    @Transactional(readOnly = false)
    @Override
    public Integer batchDelete(List<String> idList) {
        if (ListUtils.isNotEmpty(idList)) {
            return this.mapper.deleteBatchIds(idList);
        } else {
            return 0;
        }
    }

    /**
     * 修改
     * @param params
     * @return
     */
    @Transactional(readOnly = false)
    @Override
    public Integer update(TWmsReciptIntoLocPlanSaveParam params) {
        TWmsReciptIntoLocPlan entityFromDb = this.mapper.selectById(params.getId());
        if (entityFromDb == null) {
            throw new ParamException("id=" + params.getId());
        }
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        BeanUtils.copyProperties(params, entityFromDb);
        entityFromDb.preUpdate(user.getId());
        return this.mapper.updateById(entityFromDb);
    }

    /**
     * 详情
     * @param id
     * @return
     */
    @Override
    public TWmsReciptIntoLocPlanVo findById(String id) {
        return this.mapper.findById(id);
    }

    /**
     * 列表
     * @param params
     * @return
     */
    @Override
    public List<TWmsReciptIntoLocPlanVo> findAll(TWmsReciptIntoLocPlanSearchParam params) {
        return this.mapper.findAll(params);
    }



    @Transactional(readOnly = false)
    @Override
    public List<TbWmsLocation> findBestFitLocation(TbWmsMaterialReceiptLineVo tbWmsMaterialReceiptLineVo){
        List<TbWmsLocation> sameMaterialLocations =
                this.tbWmsLocationMapper.findSameMaterialLocations(tbWmsMaterialReceiptLineVo.getMaterialNo(),tbWmsMaterialReceiptLineVo.getVolume());
        if(sameMaterialLocations!=null&&sameMaterialLocations.size()>0){
            return sameMaterialLocations;
        }else{
            sameMaterialLocations =
                    this.tbWmsLocationMapper.findSameMaterialLocations(tbWmsMaterialReceiptLineVo.getMaterialNo());
            //不用比入库明细大的面积也查找出来
            //  如果装不下要继续找
            if(sameMaterialLocations!=null&&sameMaterialLocations.size()>0){
                Double locLineVol = tbWmsMaterialReceiptLineVo.getVolume();
                Double locTotRemainVol =  0.0;
                int needMoreFlag = 0;
                for(int i=0; i <sameMaterialLocations.size();i++){
                    TbWmsLocation tbWmsLocation = (TbWmsLocation)sameMaterialLocations.get(i);
                    locTotRemainVol = NumberUtils.add(locTotRemainVol,tbWmsLocation.getRemainLoad());
                    if(locTotRemainVol>=locLineVol){
                        needMoreFlag = 1;
                        break;
                    }
                }
                if(needMoreFlag==0){ //还不够
                    SkuVo sku =skuMapper.findById(tbWmsMaterialReceiptLineVo.getMaterialNo());
                    List<TbWmsLocation> ttbWmsLocations = this.findProperLocation(sku.getOutBoundFrequencyRate(),tbWmsMaterialReceiptLineVo.getVolume());
                    sameMaterialLocations.addAll(ttbWmsLocations);
                }
                return sameMaterialLocations;
            }else{
                return null; //没有装过的
            }


        }

    }


    @Transactional(readOnly = false)
    @Override
    public String genInLocPlanBySelectItem(TWmsReciptIntoLocPlanSaveParam params, String [] ids) {
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        List<TbWmsMaterialReceiptLineVo> needInLocs =new ArrayList<TbWmsMaterialReceiptLineVo>();
        for(int i=0;i<ids.length;i++){
            TbWmsMaterialReceiptLineVo tbWmsMaterialReceiptLineVo
                    = this.iTbWmsMaterialReceiptLineService.findById(ids[i]);
            needInLocs.add(tbWmsMaterialReceiptLineVo);
        }


        int seq = 1;


        this.genReciptIntoLocPlan(needInLocs,seq,user,params);

        return "success";
    }
    @Transactional(readOnly = false)
    @Override
    public String genInLocPlanBySelect(TWmsReciptIntoLocPlanSaveParam params, String [] ids) {
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        List<TbWmsMaterialReceiptLineVo> needInLocs =new ArrayList<TbWmsMaterialReceiptLineVo>();
        for(int i=0;i<ids.length;i++) {
            TbWmsMaterialReceiptLineSearchParam tbWmsMaterialReceiptLineSearchParam
                    = new TbWmsMaterialReceiptLineSearchParam();
            tbWmsMaterialReceiptLineSearchParam.setReceiptId(ids[i]);
            List<TbWmsMaterialReceiptLineVo> thisrecpt =
                    this.iTbWmsMaterialReceiptLineService.findAll(tbWmsMaterialReceiptLineSearchParam);
            needInLocs.addAll(thisrecpt);
        }
        int seq = 1;
        this.genReciptIntoLocPlan(needInLocs,seq,user,params);

        return "success";
    }
    @Transactional(readOnly = false)
    @Override
    public String handlePublish() {
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();

        TbWmsMaterialReceiptLineSearchParam tbWmsMaterialReceiptLineSearchParam
                = new TbWmsMaterialReceiptLineSearchParam();
        tbWmsMaterialReceiptLineSearchParam.setStatus(WmsInStatusEnum.created.getValue());
        List<TbWmsMaterialReceiptLineVo> needInLocs =
                this.iTbWmsMaterialReceiptLineService.findAll(tbWmsMaterialReceiptLineSearchParam);


        int seq = 1;


        return this.genPublishLocPlan(needInLocs,seq,user);



    }

    @Transactional(readOnly = false)
    public String genPublishLocPlan(List<TbWmsMaterialReceiptLineVo> needInLocs ,int seq,UserVo userVo){
        String rt ="success";

        for(int i=0; i< needInLocs.size();i++){
            TbWmsMaterialReceiptLineVo thisTbWmsMaterialReceiptLineVo = (TbWmsMaterialReceiptLineVo)needInLocs.get(i);
            TWhWarehouseCustomerMaterial tWhWarehouseCustomerMaterial =
                    this.tWhWarehouseCustomerMaterialMapper.findBySkuCode(thisTbWmsMaterialReceiptLineVo.getSkuCode());

            List<TbWmsLocation> tbWmsLocations = this.findBestFitLocation(thisTbWmsMaterialReceiptLineVo);
            if(tbWmsLocations!=null&&tbWmsLocations.size()>0){


                this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,null,userVo,UserType.pick.getEventCode());
                if(tWhWarehouseCustomerMaterial.getNeedLiftYn()!=null){

                    this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,null,userVo,UserType.lift.getEventCode());
                }

            }else{
                SkuVo sku =skuMapper.findById(thisTbWmsMaterialReceiptLineVo.getMaterialNo());
                List<TbWmsLocation> ttbWmsLocations = this.findProperLocation(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getWeight());


                this.createInLocPlan(ttbWmsLocations,thisTbWmsMaterialReceiptLineVo,null,userVo,UserType.pick.getEventCode());
                if(tWhWarehouseCustomerMaterial.getNeedLiftYn()!=null){

                    this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,null,userVo,UserType.lift.getEventCode());
                }
                //  iTbWmsLocationService.inLoc(tbWmsLocation,thisTbWmsMaterialReceiptLineVo);
            }
            thisTbWmsMaterialReceiptLineVo.setStatus(WmsInStatusEnum.planed.getValue());
            TbWmsMaterialReceiptLine entityFromDb = this.tbWmsMaterialReceiptLineMapper.selectById(thisTbWmsMaterialReceiptLineVo.getId());


            BeanUtils.copyProperties(thisTbWmsMaterialReceiptLineVo, entityFromDb);
            entityFromDb.preUpdate(userVo.getId());
            this.tbWmsMaterialReceiptLineMapper.updateById(entityFromDb);
        }
        return rt;
    }
    @Transactional(readOnly = false)
    @Override
    public String genInLocPlan() {
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();

        TbWmsMaterialReceiptLineSearchParam tbWmsMaterialReceiptLineSearchParam
                = new TbWmsMaterialReceiptLineSearchParam();
        tbWmsMaterialReceiptLineSearchParam.setStatus(WmsInStatusEnum.created.getValue());
        List<TbWmsMaterialReceiptLineVo> needInLocs =
                this.iTbWmsMaterialReceiptLineService.findAll(tbWmsMaterialReceiptLineSearchParam);


        int seq = 1;


        this.genReciptIntoLocPlan(needInLocs,seq,user);

        return "success";
    }
    @Transactional(readOnly = false)
    public List<TbWmsLocation> findProperLocationUseQty(int skuOutBoundFrequencyRate,Double qty,String skuCode){

        TWhWarehouseCustomerMaterial tWhWarehouseCustomerMaterial = this.tWhWarehouseCustomerMaterialMapper.findBySkuCode(skuCode);
        Double vol = NumberUtils.mul(tWhWarehouseCustomerMaterial.getUnitVolume().doubleValue(),qty);
        List<TbWmsLocation> tbWmsLocations = tbWmsLocationMapper.findEmptyCanUse(skuOutBoundFrequencyRate);
        //从出库指数匹配的库位开始查一直查到全部货位
        Double totRemainVol = tbWmsLocationMapper.findRemainLoadEmptyCanUse(skuOutBoundFrequencyRate);
        if(totRemainVol!=null) {
            if(totRemainVol>=vol){
                return tbWmsLocations;
            }else{
                skuOutBoundFrequencyRate++;
                Double needVol = NumberUtils.sub(vol,totRemainVol) ;
                List<TbWmsLocation> nexttbWmsLocations =this.findProperLocation(skuOutBoundFrequencyRate,needVol);
                tbWmsLocations.addAll(nexttbWmsLocations);
                return tbWmsLocations;
            }
        } else{
            throw new BusinessException("没有合适的存储空间");
        }


    }
    @Transactional(readOnly = false)
    public List<TbWmsLocation> findProperLocation(int skuOutBoundFrequencyRate,Double vol){


        List<TbWmsLocation> tbWmsLocations = tbWmsLocationMapper.findEmptyCanUse(skuOutBoundFrequencyRate);
        //从出库指数匹配的库位开始查一直查到全部货位
        Double totRemainVol = tbWmsLocationMapper.findRemainLoadEmptyCanUse(skuOutBoundFrequencyRate);
        if(totRemainVol!=null) {
            if(vol!=null){
                if(totRemainVol>=vol){
                    return tbWmsLocations;
                }else{
                    skuOutBoundFrequencyRate++;
                    Double needVol = NumberUtils.sub(vol,totRemainVol) ;
                    List<TbWmsLocation> nexttbWmsLocations =this.findProperLocation(skuOutBoundFrequencyRate,needVol);
                    tbWmsLocations.addAll(nexttbWmsLocations);
                    return tbWmsLocations;
                }
            }else{
                return tbWmsLocations;
            }

        } else{
            throw new BusinessException("没有合适的存储空间");
        }


    }
    @Transactional(readOnly = false)
    public void createInLocPlan
            (List<TbWmsLocation> tbWmsLocations,TbWmsMaterialReceiptLineVo tbWmsMaterialReceiptLineVo,
             HrEmployeeManageVo hrEmployeeManageVo,UserVo userVo,String joType){
        Double remainVol = 0.0;
        List<TbWmsLocation> heretbWmsLocations = new ArrayList<TbWmsLocation>();
        heretbWmsLocations.addAll(tbWmsLocations);
        if(tbWmsMaterialReceiptLineVo.getVolume()==null){
            if(tbWmsMaterialReceiptLineVo.getUnitVolume()!=null){
                if(tbWmsMaterialReceiptLineVo.getShipByPackOrqty().equals("pack")){
                    remainVol = NumberUtils.mul(tbWmsMaterialReceiptLineVo.getPackQty().doubleValue(),tbWmsMaterialReceiptLineVo.getUnitVolume());
                }else  if(tbWmsMaterialReceiptLineVo.getShipByPackOrqty().equals("qty")){
                    remainVol = NumberUtils.mul(tbWmsMaterialReceiptLineVo.getQuantity(),tbWmsMaterialReceiptLineVo.getUnitVolume());
                }else  if(tbWmsMaterialReceiptLineVo.getShipByPackOrqty().equals("weight")){
                    remainVol = NumberUtils.mul(tbWmsMaterialReceiptLineVo.getWeight(),tbWmsMaterialReceiptLineVo.getUnitVolume());
                }else{
                    if(tbWmsMaterialReceiptLineVo.getPackQty()!=null){
                        remainVol = NumberUtils.mul(tbWmsMaterialReceiptLineVo.getPackQty().doubleValue(),tbWmsMaterialReceiptLineVo.getUnitVolume());
                    }

                }

            }
        }else{
            remainVol=tbWmsMaterialReceiptLineVo.getVolume();
        }

        Double remainQty = tbWmsMaterialReceiptLineVo.getQuantity();

        for(int i =0;i<heretbWmsLocations.size();i++){
            TbWmsLocation tbWmsLocation = (TbWmsLocation)heretbWmsLocations.get(i);
            TWmsReciptIntoLocPlan entity = new TWmsReciptIntoLocPlan();
            entity.setLocationNo(tbWmsLocation.getLocationNo());
            entity.setCustomerName(tbWmsMaterialReceiptLineVo.getCustomerName());
            entity.setMaterialName(tbWmsMaterialReceiptLineVo.getMaterialName());
            entity.setJobType(joType);
            if(tbWmsLocation.getRemainLoad()< remainVol){
                remainVol = NumberUtils.sub(remainVol,tbWmsLocation.getRemainLoad());
                Double qty = NumberUtils.mul(remainQty,NumberUtils.div(tbWmsLocation.getRemainLoad(),tbWmsMaterialReceiptLineVo.getVolume()));
                entity.setQty(BigDecimal.valueOf(qty));
                remainQty = NumberUtils.sub(remainQty,qty);
            }else{
                entity.setQty(BigDecimal.valueOf(tbWmsMaterialReceiptLineVo.getQuantity()));
                remainVol = 0.0;
            }
            entity.setReciptLineId(tbWmsMaterialReceiptLineVo.getId());
            entity.setRequstRecptDate(new Date());
            if(hrEmployeeManageVo!=null){
                entity.setJobUserName(hrEmployeeManageVo.getPersonName());
                entity.setJobUserNo(hrEmployeeManageVo.getUserId());
                entity.setStatus("created");
            }else{
                entity.setJobUserName("任务发布");
                entity.setJobUserNo("任务发布");
                entity.setStatus("published");
            }

            entity.setId(idWorker.nextId() + "").preInsert(userVo.getId());
            this.mapper.insert(entity);
            if(remainVol<=0.0){
                break;
            }
        }
        String maxload = this.configMapper.findByConfigKey("sys.max.load");
        if(hrEmployeeManageVo!=null) {
            double jobloads = hrEmployeeManageVo.getCurrentJobLoad();
            double max = Double.valueOf(maxload);
            double thisload = NumberUtils.div(1.0, max);
            double nowload = NumberUtils.add(jobloads, thisload);

            HrEmployeeManage hrEmployeeManage = this.hrEmployeeManageMapper.selectById(hrEmployeeManageVo.getId());
            hrEmployeeManage.setCurrentJobLoad(nowload);
            hrEmployeeManage.preUpdate(userVo.getId());
            this.hrEmployeeManageMapper.updateById(hrEmployeeManage);
        }
    }
    @Transactional(readOnly = false)
    @Override
    public int getInLocJob(String id){
        UserVo user = tokenService.getLoginUser(ServletUtils.getRequest()).getUser();
        HrEmployeeManageVo dispatchuserVo = this.hrEmployeeManageMapper.findByUserId(user.getId());
        TWmsReciptIntoLocPlan tWmsReciptIntoLocPlan = this.mapper.selectById(id);
        tWmsReciptIntoLocPlan.setJobUserName(dispatchuserVo.getPersonName());
        tWmsReciptIntoLocPlan.setJobUserNo(dispatchuserVo.getId());
        tWmsReciptIntoLocPlan.setStatus("created");
        tWmsReciptIntoLocPlan.preUpdate(user.getId());
        return this.mapper.updateById(tWmsReciptIntoLocPlan);
    }
    @Transactional(readOnly = false)
    public Integer findProperRate(){
        List<TbWmsMaterialDeliveryLineVo> skuCtOutBoundList = this.tbWmsMaterialDeliveryLineMapper.findSkuCtOutBoundList();
        Integer index = skuCtOutBoundList.size()+1;
        return index;
    }
    @Transactional(readOnly = false)
    public void genReciptIntoLocPlan(List<TbWmsMaterialReceiptLineVo> needInLocs,int seq,UserVo userVo,TWmsReciptIntoLocPlanSaveParam param){
        List<HrEmployeeManageVo> pickUpUsers =new ArrayList<HrEmployeeManageVo>();
        List<HrEmployeeManageVo> liftUpUsers =new ArrayList<HrEmployeeManageVo>();
        if(param.getLiftEmployees()!=null&&param.getLiftEmployees().size()>0){
            pickUpUsers=this.iHrEmployeeManageService.findOperatorOrderByIds(param.getLiftEmployees());
        }else{
            pickUpUsers = this.iHrEmployeeManageService.findOperatorOrderByWorkloadDesc(UserType.lift.getEventCode());
        }
        if(param.getPickEmployees()!=null&&param.getPickEmployees().size()>0){
            liftUpUsers= this.iHrEmployeeManageService.findOperatorOrderByIds(param.getPickEmployees());
        }else{
            liftUpUsers = this.iHrEmployeeManageService.findOperatorOrderByWorkloadDesc(UserType.lift.getEventCode());
        }

        int pickuserIndex = 0;
        int liftuserIndex = 0;
        for(int i=0; i< needInLocs.size();i++){
            TbWmsMaterialReceiptLineVo thisTbWmsMaterialReceiptLineVo = (TbWmsMaterialReceiptLineVo)needInLocs.get(i);

            List<TbWmsLocation> tbWmsLocations = this.findBestFitLocation(thisTbWmsMaterialReceiptLineVo);
            if(tbWmsLocations!=null&&tbWmsLocations.size()>0){
                if(pickuserIndex>pickUpUsers.size()){
                    pickuserIndex = 0;
                }
                if(liftuserIndex>liftUpUsers.size()){
                    liftuserIndex = 0;
                }
                HrEmployeeManageVo hrEmployeeManageVo = (HrEmployeeManageVo)pickUpUsers.get(pickuserIndex);
                this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,hrEmployeeManageVo,userVo,UserType.pick.getEventCode());
                if(param.getNeedLiftYn()!=null){
                    HrEmployeeManageVo lfthrEmployeeManageVo = (HrEmployeeManageVo)liftUpUsers.get(pickuserIndex);
                    tbWmsLocations = this.findBestFitLocation(thisTbWmsMaterialReceiptLineVo);
                    this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,lfthrEmployeeManageVo,userVo,UserType.lift.getEventCode());
                }
                //  iTbWmsLocationService.inLoc(tbWmsLocation,thisTbWmsMaterialReceiptLineVo);
            }else{
                Sku sku =skuMapper.findBySkuCode(thisTbWmsMaterialReceiptLineVo.getSkuCode());
                if(sku.getOutBoundFrequencyRate()==null||sku.getOutBoundFrequencyRate()==1000){
                    Integer rate = this.findProperRate();
                    sku.setOutBoundFrequencyRate(rate);
                    sku.preUpdate(userVo.getId());
                    this.skuMapper.updateById(sku);
                }
                List<TbWmsLocation> ttbWmsLocations = new ArrayList<TbWmsLocation>();
                if(thisTbWmsMaterialReceiptLineVo.getVolume()!=null){
                    ttbWmsLocations = this.findProperLocation(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getVolume());

                }else{
                    ttbWmsLocations = this.findProperLocationUseQty(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getQuantity(),thisTbWmsMaterialReceiptLineVo.getSkuCode());

                }
                if(pickuserIndex>=pickUpUsers.size()){
                    pickuserIndex = 0;
                }
                if(liftuserIndex>=liftUpUsers.size()){
                    liftuserIndex = 0;
                }
                HrEmployeeManageVo hrEmployeeManageVo = (HrEmployeeManageVo)pickUpUsers.get(pickuserIndex);
                this.createInLocPlan(ttbWmsLocations,thisTbWmsMaterialReceiptLineVo,hrEmployeeManageVo,userVo,UserType.pick.getEventCode());
                if(param.getNeedLiftYn()!=null){
                    HrEmployeeManageVo lfthrEmployeeManageVo = (HrEmployeeManageVo)liftUpUsers.get(pickuserIndex);
                    if(thisTbWmsMaterialReceiptLineVo.getVolume()!=null){
                        ttbWmsLocations = this.findProperLocation(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getVolume());

                    }else{
                        ttbWmsLocations = this.findProperLocationUseQty(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getQuantity(),thisTbWmsMaterialReceiptLineVo.getSkuCode());

                    }
                    this.createInLocPlan(ttbWmsLocations,thisTbWmsMaterialReceiptLineVo,lfthrEmployeeManageVo,userVo,UserType.lift.getEventCode());
                }
                //  iTbWmsLocationService.inLoc(tbWmsLocation,thisTbWmsMaterialReceiptLineVo);
            }
            pickuserIndex++;
            thisTbWmsMaterialReceiptLineVo.setStatus(WmsInStatusEnum.planed.getValue());
            TbWmsMaterialReceiptLine entityFromDb = this.tbWmsMaterialReceiptLineMapper.selectById(thisTbWmsMaterialReceiptLineVo.getId());


            BeanUtils.copyProperties(thisTbWmsMaterialReceiptLineVo, entityFromDb);
            entityFromDb.preUpdate(userVo.getId());
             this.tbWmsMaterialReceiptLineMapper.updateById(entityFromDb);
        }
    }
    @Transactional(readOnly = false)
    public void genReciptIntoLocPlan(List<TbWmsMaterialReceiptLineVo> needInLocs,int seq,UserVo userVo){
        List<HrEmployeeManageVo> pickUpUsers = this.iHrEmployeeManageService.findOperatorOrderByWorkloadDesc(UserType.pick.getEventCode());
        List<HrEmployeeManageVo> liftUpUsers = this.iHrEmployeeManageService.findOperatorOrderByWorkloadDesc(UserType.lift.getEventCode());

        int pickuserIndex = 0;
        int liftuserIndex = 0;
        for(int i=0; i< needInLocs.size();i++){
            TbWmsMaterialReceiptLineVo thisTbWmsMaterialReceiptLineVo = (TbWmsMaterialReceiptLineVo)needInLocs.get(i);
            TWhWarehouseCustomerMaterial tWhWarehouseCustomerMaterial = this.tWhWarehouseCustomerMaterialMapper.
                    findBySkuCode(thisTbWmsMaterialReceiptLineVo.getSkuCode());

            List<TbWmsLocation> tbWmsLocations = this.findBestFitLocation(thisTbWmsMaterialReceiptLineVo);
            if(tbWmsLocations!=null&&tbWmsLocations.size()>0){
                if(pickuserIndex>pickUpUsers.size()){
                    pickuserIndex = 0;
                }
                if(liftuserIndex>liftUpUsers.size()){
                    liftuserIndex = 0;
                }
                HrEmployeeManageVo hrEmployeeManageVo = (HrEmployeeManageVo)pickUpUsers.get(pickuserIndex);
                this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,hrEmployeeManageVo,userVo,UserType.pick.getEventCode());
                if(tWhWarehouseCustomerMaterial.getNeedLiftYn()!=null){
                    HrEmployeeManageVo lfthrEmployeeManageVo = (HrEmployeeManageVo)liftUpUsers.get(pickuserIndex);
                    this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,lfthrEmployeeManageVo,userVo,UserType.lift.getEventCode());
                }
                //  iTbWmsLocationService.inLoc(tbWmsLocation,thisTbWmsMaterialReceiptLineVo);
            }else{
                Sku sku =skuMapper.findBySkuCode(thisTbWmsMaterialReceiptLineVo.getSkuCode());
                if(sku.getOutBoundFrequencyRate()==null||sku.getOutBoundFrequencyRate()==1000){
                    Integer rate = this.findProperRate();
                    sku.setOutBoundFrequencyRate(rate);
                    sku.preUpdate(userVo.getId());
                    this.skuMapper.updateById(sku);
                }
                List<TbWmsLocation> ttbWmsLocations = this.findProperLocation(sku.getOutBoundFrequencyRate(),thisTbWmsMaterialReceiptLineVo.getWeight());
                if(pickuserIndex>=pickUpUsers.size()){
                    pickuserIndex = 0;
                }
                HrEmployeeManageVo hrEmployeeManageVo = (HrEmployeeManageVo)pickUpUsers.get(pickuserIndex);
                this.createInLocPlan(ttbWmsLocations,thisTbWmsMaterialReceiptLineVo,hrEmployeeManageVo,userVo,UserType.pick.getEventCode());
                if(tWhWarehouseCustomerMaterial.getNeedLiftYn()!=null){
                    HrEmployeeManageVo lfthrEmployeeManageVo = (HrEmployeeManageVo)liftUpUsers.get(pickuserIndex);
                    this.createInLocPlan(tbWmsLocations,thisTbWmsMaterialReceiptLineVo,lfthrEmployeeManageVo,userVo,UserType.lift.getEventCode());
                }
                //  iTbWmsLocationService.inLoc(tbWmsLocation,thisTbWmsMaterialReceiptLineVo);
            }
            pickuserIndex++;
            thisTbWmsMaterialReceiptLineVo.setStatus(WmsInStatusEnum.planed.getValue());
            TbWmsMaterialReceiptLine entityFromDb = this.tbWmsMaterialReceiptLineMapper.selectById(thisTbWmsMaterialReceiptLineVo.getId());


            BeanUtils.copyProperties(thisTbWmsMaterialReceiptLineVo, entityFromDb);
            entityFromDb.preUpdate(userVo.getId());
            this.tbWmsMaterialReceiptLineMapper.updateById(entityFromDb);
        }
    }
    /**
     * 列表-分页
     * @param params
     * @param current
     * @param pageSize
     * @return
     */
    @Override
    public IPage<TWmsReciptIntoLocPlanVo> findAll(TWmsReciptIntoLocPlanSearchParam params, Integer current, Integer pageSize) {
        return this.mapper.findAll(new Page<>(current, pageSize), params);
    }

}
